package com.dykj.fireFighting.web.onenet.service.impl;

import com.alibaba.fastjson.JSON;
import com.dykj.fireFighting.api.base.emergency.entity.EmergencyStaff;
import com.dykj.fireFighting.api.base.emergency.service.IEmergencyStaffService;
import com.dykj.fireFighting.api.base.news.service.IAliMessageService;
import com.dykj.fireFighting.common.core.constant.WebsocketConstant;
import com.dykj.fireFighting.common.starter.redisson.service.RedisService;
import com.dykj.fireFighting.web.base.websocket.entity.MoreMessage;
import com.dykj.fireFighting.web.model.Device;
import com.dykj.fireFighting.web.model.report.DevHisWater;
import com.dykj.fireFighting.web.model.vo.SocialUnitVo;
import com.dykj.fireFighting.web.onenet.service.WaterTopRuiService;
import com.dykj.fireFighting.web.rocketmq.message.WaterPushMessage;
import com.dykj.fireFighting.web.rocketmq.producer.InsertDevHisWaterProducer;
import com.dykj.fireFighting.web.rocketmq.producer.WaterPushProducer;
import com.dykj.fireFighting.web.service.DevHisService;
import com.dykj.fireFighting.web.service.SysUserService;
import com.dykj.fireFighting.web.utils.UUIDUtils;
import net.sf.json.JSONObject;
import org.apache.dubbo.config.annotation.DubboReference;
import org.apache.rocketmq.client.producer.SendCallback;
import org.apache.rocketmq.client.producer.SendResult;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;

import java.text.SimpleDateFormat;
import java.util.ArrayList;
import java.util.Date;
import java.util.List;
import java.util.Map;

@Service
public class WaterTopRuiServiceImpl implements WaterTopRuiService {
    @Autowired
    private RedisService redisService;
    @Autowired
    private DevHisService devHisService;
    @Autowired
    private SysUserService sysUserService;
    @Autowired
    private InsertDevHisWaterProducer insertDevHisWaterProducer;
    @Autowired
    private WaterPushProducer waterPushProducer;
    @DubboReference
    private IAliMessageService aliMessageService;
    @DubboReference
    private IEmergencyStaffService iEmergencyStaffService;

    @Override
    public void putTopRiPressureToMQ(Object obj,String str) {
        JSONObject jsonMsg = JSONObject.fromObject(obj);
        //查询设备，有设备继续，无设备return
        String devId = jsonMsg.getString("imei");
        Device device = JSON.parseObject((String) redisService.get(devId), Device.class);
        if (device == null) {
            device = devHisService.queryCreateBy(devId);
        }
        if (device == null) {
            return;
        }
        redisService.set(devId, JSON.toJSONString(device));

        //示例数据
        //{"at":1642490169670,"imei":"862657051591265","type":1,"ds_id":"3200_0_5750","value":"{\"t\":\"20220118151600\",\"F\":0.0000,\"T\":19.0,\"V\":99.57,\"Q\":23,\"R\":76}","dev_id":882256092}

        String type = jsonMsg.getString("type");
        //上下线
        if (2 == Integer.parseInt(type)) {
            String status= jsonMsg.getString("status");
            if (status.equals("0")){
                device.setStatus("设备离线");
            }else {
                device.setStatus("设备上线");

            }
            //获取推送人信息
            DevHisWater devHisWater = new DevHisWater();
            SocialUnitVo socialUnitVo = getContacts(device);
            devHisWater.setUnitId(device.getUnitId());
            devHisWater.setUnitName(device.getUnitName());
            devHisWater.setCenterUnitId(socialUnitVo.getCenterUnitId());
            SimpleDateFormat sdf = new SimpleDateFormat("yyyy-MM-dd HH:mm:ss");
            String time =sdf.format(new Date());
            devHisWater.setUploadTime(time);
            devHisWater.setRelationId(device.getRelationId());
            devHisWater.setManufactorIdentification(device.getRelationId());
            devHisWater.setId(UUIDUtils.getTimeUUID());
            devHisWater.setDeviceName(device.getName());
            devHisWater.setComponentStatus(device.getStatus());
            devHisWater.setStateTime(stampToDate(jsonMsg.getString("at")));
            //入数据库
            insertDevHisWaterProducer.asyncSend(devHisWater, new SendCallback() {
                @Override
                public void onSuccess(SendResult sendResult) {
                    System.out.println("=======发送插入拓普瑞上下线消息成功=======");
                }

                @Override
                public void onException(Throwable throwable) {
                    System.out.println("=======发送插入拓普瑞上下线消息失败=======");
                }
            });
            //上线通知推送
            MoreMessage moreMessage = new MoreMessage();
            moreMessage.setUserIds(socialUnitVo.getUnitUserIds().toArray(new String[0]));
            moreMessage.setCmd(WebsocketConstant.CMD_TOPIC);
            //moreMessage.setMsgId(devHis.getId());
            moreMessage.setMsgId(devHisWater.getId());
            moreMessage.setMsgTitle("主机上线通知");
            moreMessage.setMsgTxt(device.getName() + "于" + devHisWater.getStateTime() + "已上线");
            redisService.convertAndSend("channel:moreMessage", moreMessage);
            return;
        }

        if (1 != Integer.parseInt(type)) {
            return;
        }
        String value = jsonMsg.getString("value");
        //暂时不接收json array
        if (value.startsWith("[")) {
            return;
        }
        String at = jsonMsg.getString("at");
        JSONObject jsonValue = JSONObject.fromObject(value);
        System.out.println("打印value值:===  " + value);
        //处理阈值数据
        if (jsonValue.has("ICCID")){
            String FH = jsonValue.getString("FH");
            String FL = jsonValue.getString("FL");
            device.setThresholdH(Double.parseDouble(FH));
            device.setThresholdL(Double.parseDouble(FL));
            devHisService.updateTopRui(device);
            return;
        }
        if (jsonValue.has("ID")) {
            //处理报警: websockt推送、MQ入库
            String ID = jsonValue.getString("ID");
            String res = alarmHandler(ID,str);

            boolean pushSwitch = true;
            int alarmNum = 0;
            Object object = redisService.get(device.getRelationId() + "_alarmNum");
            if (object != null) {
                alarmNum = (int) object;
            }
            if (alarmNum > device.getAlarmNumber()) {
                pushSwitch = false;
            }
            String ACTION = jsonValue.getString("ACTION");
            if (ACTION.equals("0")){
                res=huiFUHandler(ID,str);
                pushSwitch = true;
            }
            //获取推送人信息
            DevHisWater devHisWater = new DevHisWater();
            SocialUnitVo socialUnitVo = getContacts(device);
            devHisWater.setUnitId(device.getUnitId());
            devHisWater.setUnitName(device.getUnitName());
            devHisWater.setCenterUnitId(socialUnitVo.getCenterUnitId());
            SimpleDateFormat sdf = new SimpleDateFormat("yyyy-MM-dd HH:mm:ss");
            String time =sdf.format(new Date());
            devHisWater.setUploadTime(time);
            devHisWater.setRelationId(device.getRelationId());
            devHisWater.setManufactorIdentification(device.getRelationId());
            devHisWater.setId(UUIDUtils.getTimeUUID());
            devHisWater.setDeviceName(device.getName());
            device.setStatus(res);
            device.setCalculationValue(Double.parseDouble(jsonValue.getString("F")) );
            devHisWater.setCalculationValue(device.getCalculationValue());
            devHisWater.setComponentStatus(device.getStatus());
            devHisWater.setStateTime(stampToDate(at));
            if (str.equals("压力")) {
                devHisWater.setMoniType("1");
            }else {
                devHisWater.setMoniType("0");
            }
            device.setT(jsonValue.getString("T"));
            device.setV(jsonValue.getString("V"));
            device.setQ(jsonValue.getString("Q"));
            //实时数据
            redisService.set(devId+"_realtime", JSON.toJSONString(device));

            if (pushSwitch) {
                //发送短信
                List<EmergencyStaff> emergencyStaffList;
                emergencyStaffList = getWaterEgencyStaffList(device.getUnitId());
                if (emergencyStaffList.size()>0) {
                    aliMessageService.sendAliMessageBatch(emergencyStaffList, "唐山臻旭科技有限公司", "SMS_213772600", device.getName(), devHisWater.getStateTime(), devHisWater.getComponentStatus());
                }
                redisService.set(device.getRelationId() + "_alarmNum", alarmNum + 1);
                //推送消息
                WaterPushMessage waterPushMessage = new WaterPushMessage();
                waterPushMessage.setDeviceName(device.getName());
                waterPushMessage.setDevice(device);
                waterPushMessage.setAlarmTime(devHisWater.getUploadTime());
                waterPushMessage.setDevHisId(devHisWater.getId());
                waterPushMessage.setUnit(socialUnitVo);
                waterPushProducer.asyncSend(waterPushMessage, new SendCallback() {
                    @Override
                    public void onSuccess(SendResult sendResult) {
                        System.out.println("=======发送拓普瑞压力推送消息成功=======");
                    }

                    @Override
                    public void onException(Throwable throwable) {
                        System.out.println("=======发送拓普瑞压力推送消息失败=======");
                    }
                });
            }
            //入数据库
            insertDevHisWaterProducer.asyncSend(devHisWater, new SendCallback() {
                @Override
                public void onSuccess(SendResult sendResult) {
                    System.out.println("=======发送插入拓普瑞压力历史记录消息成功=======");
                }

                @Override
                public void onException(Throwable throwable) {
                    System.out.println("=======发送插入拓普瑞压力历史记录消息失败=======");
                }
            });
        } else {
            //处理正常数据
            device.setCalculationValue(Double.parseDouble(jsonValue.getString("F")) );
            device.setT(jsonValue.getString("T"));
            device.setV(jsonValue.getString("V"));
            device.setQ(jsonValue.getString("Q"));
            device.setStatus("正常");
            redisService.set(devId+"_realtime", JSON.toJSONString(device));
            redisService.del(device.getRelationId() + "_alarmNum");
        }

    }

    private String alarmHandler(String ID,String str) {
        String result;
        switch (ID) {
            case "1":
                result=str+"高限报警";
                break;
            case "2":
                result=str+"低限报警";
                break;
            case "3":
                result="波动超限报警";
                break;
            case "4":
                result="温度超限报警";
                break;
            case "5":
                result="温度低限报警";
                break;
            case "6":
                result="温度波动超限报警";
                break;
            case "7":
                result="传感器故障";
                break;
            case "8":
                result="存储故障";
                break;
            case "9":
                result="电池电量报警";
                break;
            default:
                result="设备数据错误";
                break;
        }
        return result;
    }

    private String huiFUHandler(String ID,String str) {
        String result;
        switch (ID) {
            case "1":
            case "2":
                result=str+"恢复";
                break;
            case "3":
                result="波动超限恢复";
                break;
            case "4":
                result="温度超限恢复";
                break;
            case "5":
                result="温度低限恢复";
                break;
            case "6":
                result="温度波动超限恢复";
                break;
            case "7":
                result="传感器故障恢复";
                break;
            case "8":
                result="存储故障恢复";
                break;
            case "9":
                result="电池电量恢复";
                break;
            default:
                result="设备数据错误";
                break;
        }
        return result;
    }

    private SocialUnitVo getContacts(Device device) {
        SocialUnitVo unit = JSON.parseObject((String) redisService.get(device.getRelationId() + "-unit"), SocialUnitVo.class);
        if (null == unit) {
            unit = new SocialUnitVo();
            Map<String, Object> centerUnit = sysUserService.getCenterUnit(device.getUnitId());
            unit.setCenterUnitId(centerUnit.get("id").toString());
            unit.setUnitUserIds(sysUserService.getUserByUnitId(device.getUnitId()));
            unit.setCenterUserIds(sysUserService.getCenterUserByUnitId(device.getUnitId()));

            List<String> idList = sysUserService.getUnitIds(device.getUnitId());
            List<String> centerIds = unit.getCenterUserIds();
            List<String> unitIds = new ArrayList<>();
            for (String centerid : centerIds) {
                for (String unitid : idList) {
                    unitIds.add(centerid + "-" + unitid);
                }
            }
            unit.setUnitIds(unitIds);

            redisService.set(device.getRelationId() + "-unit", JSON.toJSONString(unit));
        }
        return unit;
    }

    public String stampToDate(String s) {
        String res;
        SimpleDateFormat simpleDateFormat = new SimpleDateFormat("yyyy-MM-dd HH:mm:ss");
        long lt = new Long(s);
        Date date = new Date(lt);
        res = simpleDateFormat.format(date);
        return res;
    }

    private List<EmergencyStaff> getWaterEgencyStaffList(String unitId) {
        return iEmergencyStaffService.getWaterStaffByUnitid(unitId);
    }
}
